<html>
<head>
<title>Rococoa Memory Management</title>
<meta content="text/html; charset=UTF-8" http-equiv="Content-Type" />           
<meta http-equiv="Content-Type" content="text/html;charset=UTF-8" />
<link rel="stylesheet" type="text/css" href="rococoa.css" title="Default" />
</head>
<body>

<h1>Rococoa Memory Management</h1>

<p>While Java has garbage collection, Objective-C memory management (prior to v2)
is based around manual reference counting.</p>

<p><a href="http://developer.apple.com/documentation/Cocoa/Conceptual/MemoryMgmt/MemoryMgmt.html">
Essentially</a>, objects have a reference count, 1 when first created, and
incremented by calling <code>- (id)retain</code>. On calling <code>- (void)release</code> 
the count is decremented, and if it has fallen to 0, the object's memory is reclaimed.</p>

<p>Conventionally, newly created objects are put into an autorelease pool, which
<code>retain</code>s them, and when the pool itself is reclaimed, all of its
objects are <code>release</code>d. If an object should live longer 
than the current pool, then client code should <code>retain</code> the object
itself, and release when done with.</p>

<p>Rococoa automatically <code>retain</code>s Objective-C objects wrapped by the
Java NSObject, and <code>release</code>s them when the Java NSObject is garbage 
collected. So why am I bothering you with all this detail? Because you need an
autorelease pool in the first place.</p>

<p>At the moment the way Rococoa creates a pool is through 
<code>ID Foundation.createPool()</code>, releasing it with
<code>void Foundation.releasePool(ID pool)</code>. It's your job to make sure that
there is a current pool before you invoke any Objective-C methods which need to 
allocate from it. For example, RococoaTestCase says 

<pre class="block">    
    public void runBare() throws Throwable {
        pool = Foundation.createPool();
        try {
            super.runBare();
        } finally {
            Foundation.releasePool(pool);
        }
    }
</pre>

thus giving each test run its own pool.</p>

<p>Helpfully, if you forget to create a pool, the Objective-C runtime will gently
chastise you on stderr with messages like 
<code>*** _NSAutoreleaseNoPool(): Object 0x1222a0 of class NSCFString autoreleased with no pool in place - just leaking</code></p>
 
<p>Note that while a pool is required during allocation, objects can outlive 
their pool, and will if you keep a reference to a Java NSObject.</p>

<p>I plan to replace those nasty calls to Foundation with a Java NSAutoreleasePool 
which you can just hang onto by reference. But the current system works, and it's 
best to be conservative about memory, as accessing an already disposed object
will crash your app. Actually I'm pretty sure that there's at least one bug hiding in there
already - a small prize to anyone who finds it.</p>

<p>Finally, note that if your code has been called by the Cocoa event thread (as
a result of a native button press for example) then Cocoa will already have 
arranged a pool for you, and will dispose of it once the event is done.</p>

<p>Really finally, I've no idea how this all relates to Objective-C garbage collection,
introduced in v2, and am hoping that someone will be able to tell me.</p>
</body>
</html>



